#include "QNumberProperty.h"

#include <QDoubleSpinBox>
#include <QSpinBox>
#include <QSizePolicy>

#include "private/QProperty_p.h"

using namespace QPE;


const int QIntegerProperty::StandardMin = -1000000;
const int QIntegerProperty::StandardMax = 1000000;

QIntegerProperty::QIntegerProperty(const QString& name, const QMap<QString, QVariant>& settings)
	: QProperty(name, QVariant::Int), Min(StandardMin), Max(StandardMax)
{
	QProperty::setSettings(settings);
	d_ptr->VariantValue.setValue(0);
	d_ptr->VariantValue.convert(QVariant::Int);
}

QIntegerProperty::QIntegerProperty(const QString &name)
	: QProperty(name), Min(StandardMin), Max(StandardMax)
{
	d_ptr->VariantValue.setValue(0);
	d_ptr->VariantValue.convert(QVariant::Int);
}

//! Returns an editor widget, or NULL if it doesn't supply one
QWidget* QIntegerProperty::createEditor(QWidget * parent, const QStyleOptionViewItem& options, const QAbstractItemDelegate* delegate)
{
	Q_UNUSED(options);
	Q_UNUSED(delegate);

	QSpinBox* tmpEditor = new QSpinBox(parent);
	tmpEditor->setMinimum(Min);
	tmpEditor->setMaximum(Max);
	tmpEditor->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
	tmpEditor->setValue(d_ptr->VariantValue.toInt());

	return tmpEditor;
}

//! Gets the data from the widget
QVariant QIntegerProperty::getEditorData(QWidget* editor) const
{
	QSpinBox* tmpEditor = qobject_cast<QSpinBox*>(editor);
	if(tmpEditor)
		return tmpEditor->value();

	return QVariant(0);
}

void QIntegerProperty::setSettings(int minimum, int maxiumum)
{
	Min = minimum;
	Max = maxiumum;
}

void QIntegerProperty::setSetting(const QString& key, const QVariant& value)
{
	if(key == "Min")
		setSettings(value.toInt(), Max);
	else if(key == "Max")
		setSettings(Min, value.toInt());
}

QVariant QIntegerProperty::getSetting(const QString& key) const
{
	if(key == "Min")
		return Min;
	if(key == "Max")
		return Max;
	else
		return QProperty::getSetting(key);
}

QStringList QIntegerProperty::getSettingKeys() const
{
	return (QStringList("Min") << "Max");
}

QString QIntegerProperty::type() const
{
	return "integer";
}

QProperty* QIntegerProperty::clone(bool include_children, QProperty* container) const
{
	return QProperty::clone(include_children, container ? container : new QIntegerProperty(getName()));
}





const double QDoubleProperty::StandardPrecision = 5;

QDoubleProperty::QDoubleProperty(const QString& name, const QMap<QString, QVariant>& settings)
	: QIntegerProperty(name), Precision(StandardPrecision)
{
	QProperty::setSettings(settings);
	d_ptr->VariantValue.setValue(0);
	d_ptr->VariantValue.convert(QVariant::Double);
	d_ptr->PropertyVariantType = QVariant::Double;
}

QDoubleProperty::QDoubleProperty(const QString &name)
	: QIntegerProperty(name), Precision(StandardPrecision)
{
	d_ptr->VariantValue.setValue(0);
	d_ptr->VariantValue.convert(QVariant::Double);
	d_ptr->PropertyVariantType = QVariant::Double;
}

//! Returns an editor widget, or NULL if it doesn't supply one
QWidget* QDoubleProperty::createEditor(QWidget * parent, const QStyleOptionViewItem& options, const QAbstractItemDelegate* delegate)
{
	Q_UNUSED(options);
	Q_UNUSED(delegate);
	QDoubleSpinBox* tmpEditor = new QDoubleSpinBox(parent);
	tmpEditor->setMinimum(Min);
	tmpEditor->setMaximum(Max);
	tmpEditor->setDecimals(Precision);
	tmpEditor->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
	tmpEditor->setValue(d_ptr->VariantValue.toDouble());

	return tmpEditor;
}

//! Gets the data from the widget
QVariant QDoubleProperty::getEditorData(QWidget* editor) const
{
	QDoubleSpinBox* tmpEditor = qobject_cast<QDoubleSpinBox*>(editor);
	if(tmpEditor)
		return tmpEditor->value();

	return QVariant(0);
}

void QDoubleProperty::setSettings(double minimum, double maxiumum, int precision)
{
	QIntegerProperty::setSettings(minimum, maxiumum);
	Precision = precision;
}

void QDoubleProperty::setSetting(const QString& key, const QVariant& value)
{
	if(key == "Min")
		setSettings(value.toDouble(), Max, Precision);
	else if(key == "Max")
		setSettings(Min, value.toDouble(), Precision);
	else if(key == "Precision")
		setSettings(Min, Max, value.toDouble());
}

QVariant QDoubleProperty::getSetting(const QString& key) const
{
	if(key == "Min")
		return Min;
	if(key == "Max")
		return Max;
	if(key == "Precision")
		return Precision;
	else
		return QProperty::getSetting(key);
}

QStringList QDoubleProperty::getSettingKeys() const
{
	return (QStringList("Min") << "Max" << "Precision");
}

QString QDoubleProperty::type() const
{
	return "double";
}

QProperty* QDoubleProperty::clone(bool include_children, QProperty* container) const
{
	return QIntegerProperty::clone(include_children, container ? container : new QDoubleProperty(getName()));
}
